//by hbs
#include <bits/stdc++.h>
using namespace std;

#define N 100010

int n,m,length,limit,pos[N],ans,ans2;
bool flag[N];

struct node
{
    int distance,v,a;
    int beg=-1,last=-1;
} car[N];

inline int rd()
{
    register int f=1,m=0;
    register char ch=getchar();
    while(ch<'0'||ch>'9')
    {
        if(ch=='-')
            f=-1;
        ch=getchar();
    }
    while(ch>='0'&&ch<='9')
    {
        m=(m<<3)+(m<<1)+(ch^48);
        ch=getchar();
    }
    return f*m;
}

void init()
{
    for(int i=1;i<=n;++i)
    {
        if(car[i].a==0)
        {
            if(car[i].v>limit)
            {
                car[i].beg=car[i].distance;
                car[i].last=length+1;
            }
        }
        else if(car[i].a>0)
        {
            if(car[i].v>limit)
            {
                car[i].beg=car[i].distance;
                car[i].last=length+1;
            }
            else
            {
                int cnt=(limit*limit-car[i].v*car[i].v)/(2*car[i].a);
                car[i].beg=min(length+1,car[i].distance+cnt+1),car[i].last=length+1;
            }
        }
        else
        {
            if(car[i].v>limit)
            {
                int cnt=(limit*limit-car[i].v*car[i].v)/(2*car[i].a);
                if((limit*limit-car[i].v*car[i].v)%(2*car[i].a)==0)
                    car[i].last=min(length+1,car[i].distance+cnt-1),car[i].beg=car[i].distance;
                else
                    car[i].last=min(length+1,car[i].distance+cnt),car[i].beg=car[i].distance; 
            }
        }
    }
}

int operation1()
{
    int res=0;
    for(int i=1;i<=n;++i)
    {
        for(int j=1;j<=m;++j)
        {
            if(car[i].beg<=pos[j]&&car[i].last>=pos[j])
            {
                ++res;
                break;
            }
        }
    }
    return res;
}

void operation2(int p,int cnt,int res)
{
    if(p>m)
    {
        int count2=0;
        for(int i=1;i<=n;++i)
        {
            for(int j=1;j<=m;++j)
            {
                if(car[i].beg<=pos[j]&&car[i].last>=pos[j]&&!flag[j])
                {
                    ++count2;
                    break;
                }
            }
        }
        if(count2==res)
            ans2=min(ans2,cnt);
        return;
    }
    operation2(p+1,cnt,res);
    flag[p]=1;
    operation2(p+1,cnt-1,res);
    flag[p]=0;
}

int main()
{
    //remember to clear when the number is removed
    freopen("detect.in", "r", stdin);
    freopen("detect.out", "w", stdout);
    int T=rd();
    for(int t=1;t<=T;++t)
    {
        for(int i=1;i<=n;++i)
            car[i].distance=car[i].a=car[i].v=car[i].last=0,car[i].beg=car[i].last=-1;//clear
        for(int i=1;i<=m;++i)
            pos[i]=-1;
        n=rd(),m=rd(),length=rd(),limit=rd();
        for(int i=1;i<=n;++i)
        {
            car[i].distance=rd();
            car[i].v=rd();
            car[i].a=rd();
        }
        for(int i=1;i<=m;++i)
            pos[i]=rd();
        init();
        ans=operation1();
        ans2=m;
        printf("%d ",ans);
        operation2(1,m,ans);
        printf("%d\n",(m-ans2));
    }
    return 0;
}